package org.javaforever.gatescore.core;

import java.util.ArrayList;
import java.util.List;
import java.util.Set;

public class UtilsMethodGenerator {
	public static StatementList generateBuildParamsStatements(FrontDomain domain, FrontVar listQuery,FrontVar postForm) {
		List<Writeable> sList = new ArrayList<Writeable>();
		sList.add(new Statement(1000L,0,"buildParams("+listQuery.getVarName()+", "+postForm.getVarName()+") {"));
		sList.add(new Statement(2000L,1,"return {"));
		sList.add(new Statement(3000L,2,"page: "+listQuery.getVarName()+".page,"));
		sList.add(new Statement(4000L,2,"rows: "+listQuery.getVarName()+".rows,"));
		long serial = 5000L;
		for (FrontField f:domain.getAllFieldsWithoutId()) {
			sList.add(new Statement(serial,2,f.getFieldName()+": "+postForm.getVarName()+"."+f.getFieldName()+","));
			serial += 1000L;
		}
		sList.add(new Statement(serial,1,"}"));
		sList.add(new Statement(serial+1000L,1,"},"));
		return WriteableUtil.merge(sList);
	}
	
	public static StatementList generateBuildIdsStatements(FrontDomain domain, FrontVar data) {
		List<Writeable> sList = new ArrayList<Writeable>();
		sList.add(new Statement(1000L,1,"buildIds("+data.getVarName()+"){"));
		sList.add(new Statement(2000L,1,"var retVal = \"\";"));
		sList.add(new Statement(3000L,1,"for (var i=0;i<"+data.getVarName()+".length;i++){"));
		sList.add(new Statement(4000L,2,"retVal += "+data.getVarName()+"[i]."+domain.getDomainId().getFieldName()+" + \",\";"));
		sList.add(new Statement(5000L,1,"}"));
		sList.add(new Statement(6000L,1,"if (retVal.indexOf(\",\")>=0) retVal = retVal.substring(0,retVal.length-1);"));
		sList.add(new Statement(7000L,1,"return retVal;"));
		sList.add(new Statement(8000L,1,"},"));
		return WriteableUtil.merge(sList);
	}

	public static StatementList generateDataBlockStatements(FrontDomain domain, FrontVar listQuery,FrontVar postForm, FrontVar defaultForm, FrontVar pagevars,Set<FrontDomain> dpDomains) {
		List<Writeable> sList = new ArrayList<Writeable>();
		sList.add(new Statement(1000L,0,"data() {"));
		sList.add(new Statement(2000L,1,"return {"));
		sList.add(new Statement(3000L,1,postForm.getVarName()+": Object.assign({}, "+defaultForm.getVarName()+"),"));
		sList.add(new Statement(4000L,1,"list: [],"));
		sList.add(new Statement(5000L,1,"selectList: [],"));
		sList.add(new Statement(6000L,1,"selectRows: [],"));
		sList.add(new Statement(7000L,1,"total: 0,"));
		sList.add(new Statement(8000L,1,"listLoading: true,"));
		sList.add(new Statement(9000L,1,"cellValue: null,"));
		sList.add(new Statement(10000L,1,"addDialogVisible: false,"));
		sList.add(new Statement(11000L,1,"editDialogVisible: false,"));
		sList.add(new Statement(12000L,1,"form:{},"));
		long serial = 13000L;
		for (FrontDomain d: dpDomains) {
			sList.add(new Statement(serial,1,"active"+d.getCapFirstPlural()+":{},"));
			sList.add(new Statement(serial+1000L,1,"init"+d.getCapFirstDomainName()+"Store: "+pagevars.getVarName()+".init"+d.getCapFirstDomainName()+"Store,"));
			serial += 2000L;
		}
		sList.add(new Statement(serial,1,listQuery.getVarName()+": {"));
		sList.add(new Statement(serial+1000L,2,"page: 1,"));
		sList.add(new Statement(serial+2000L,2,"rows: 10"));
		sList.add(new Statement(serial+3000L,1,"}"));
		sList.add(new Statement(serial+4000L,1,"}"));
		sList.add(new Statement(serial+5000L,0,"},"));
		return WriteableUtil.merge(sList);
	}
	
	public static StatementList generateCreatedBlockStatements(FrontDomain domain,Set<FrontDomain> dpDomains) {
		List<Writeable> sList = new ArrayList<Writeable>();
		sList.add(new Statement(1000L,0,"created() {"));
		long serial = 2000L;
		for (FrontDomain d: dpDomains) {
			sList.add(new Statement(serial,1,"this.init"+d.getCapFirstDomainName()+"Store();"));
			sList.add(new Statement(serial+1000L,1,"this.listActive"+d.getCapFirstPlural()+"();"));
			serial += 2000L;
		}
		sList.add(new Statement(serial,1,"this.search"+domain.getCapFirstPlural()+"ByFieldsByPage();"));
		sList.add(new Statement(serial+1000L,0,"},"));
		return WriteableUtil.merge(sList);
	}
	
	public static StatementList generateDefaultFormBlockStatements(FrontDomain domain,FrontVar defaultForm) {
		List<Writeable> sList = new ArrayList<Writeable>();
		sList.add(new Statement(1000L,0,"const defaultForm = {"));
		long serial = 2000L;
		for (FrontField f:domain.getAllFieldsWithoutId()) {
			sList.add(new Statement(serial,2,f.getFieldName()+": '',"));
			serial += 1000L;
		}
		sList.add(new Statement(serial,1,"}"));
		return WriteableUtil.merge(sList);
	}
	
	public static StatementList generateDomainFilterStatements(FrontDomain domain, FrontVar pagevars) {
		List<Writeable> sList = new ArrayList<Writeable>();
		sList.add(new Statement(1000L,1,domain.getLowerFirstDomainName()+"Filter("+domain.getDomainId().getFieldName()+") {"));
		sList.add(new Statement(2000L,1,"while ("+pagevars.getVarName()+"."+domain.getLowerFirstDomainName()+"Store."+domain.getLowerFirstDomainName()+"Map == null) this.sleep(100);"));
		sList.add(new Statement(3000L,1,"return "+pagevars.getVarName()+"."+domain.getLowerFirstDomainName()+"Store."+domain.getLowerFirstDomainName()+"Map["+domain.getDomainId().getFieldName()+"];"));
		sList.add(new Statement(4000L,1,"},"));
		return WriteableUtil.merge(sList);
	}
	
	public static StatementList generateSleepMethodStatements() {
		List<Writeable> sList = new ArrayList<Writeable>();
		sList.add(new Statement(1000L,1,"sleep(delay) {"));
		sList.add(new Statement(2000L,2,"var start = (new Date()).getTime();"));
		sList.add(new Statement(3000L,2,"while ((new Date()).getTime() - start < delay) {"));
		sList.add(new Statement(4000L,3,"continue;"));
		sList.add(new Statement(5000L,2,"}"));
		sList.add(new Statement(6000L,1,"},"));
		return WriteableUtil.merge(sList);
	}
	
	public static StatementList generateConfirmDeleteMethodStatements(FrontDomain domain) {
		List<Writeable> sList = new ArrayList<Writeable>();
		sList.add(new Statement(1000L,1,"confirmDelete(){"));
		sList.add(new Statement(2000L,1,"this.$confirm('确定要删除"+domain.getText()+"?', '删除警告', {"));
		sList.add(new Statement(3000L,2,"confirmButtonText: '确定',"));
		sList.add(new Statement(4000L,2,"cancelButtonText: '取消',"));
		sList.add(new Statement(5000L,2,"type: 'warning'"));
		sList.add(new Statement(6000L,2,"}).then(() => {"));
		sList.add(new Statement(7000L,2,"delete"+domain.getCapFirstDomainName()+"(this.selectList[0].id).then(response => {"));
		sList.add(new Statement(8000L,3,"this.reload();"));
		sList.add(new Statement(9000L,2,"});"));
		sList.add(new Statement(10000L,2,"}).catch(() => {"));
		sList.add(new Statement(11000L,2,"});"));
		sList.add(new Statement(12000L,1,"},"));
		return WriteableUtil.merge(sList);
	}
	
	public static StatementList generateConfirmDeleteAllMethodStatements(FrontDomain domain) {
		List<Writeable> sList = new ArrayList<Writeable>();
		sList.add(new Statement(1000L,1,"confirmDeleteAll(data){"));
		sList.add(new Statement(2000L,1,"this.$confirm('确定要批删除"+domain.getText()+"?', '批删除警告', {"));
		sList.add(new Statement(3000L,2,"confirmButtonText: '确定',"));
		sList.add(new Statement(4000L,2,"cancelButtonText: '取消',"));
		sList.add(new Statement(5000L,2,"type: 'warning'"));
		sList.add(new Statement(6000L,2,"}).then(() => {"));
		sList.add(new Statement(7000L,2,"deleteAll"+domain.getCapFirstPlural()+"(this.buildIds(data)).then(response => {"));
		sList.add(new Statement(8000L,3,"this.reload();"));
		sList.add(new Statement(9000L,2,"});"));
		sList.add(new Statement(10000L,2,"}).catch(() => {"));
		sList.add(new Statement(11000L,2,"});"));
		sList.add(new Statement(12000L,1,"},"));
		return WriteableUtil.merge(sList);
	}
	
	public static StatementList generateHandleSizeChangeMethodStatements(FrontVar listQuery) {
		List<Writeable> sList = new ArrayList<Writeable>();
		sList.add(new Statement(1000L,1,"handleSizeChange(val) {"));
		sList.add(new Statement(2000L,1,"this."+listQuery.getVarName()+".page = val"));
		sList.add(new Statement(3000L,1,"this.getList()"));
		sList.add(new Statement(4000L,1,"},"));
		return WriteableUtil.merge(sList);
	}	
	
	public static StatementList generateHandleCurrentChangeMethodStatements(FrontVar listQuery) {
		List<Writeable> sList = new ArrayList<Writeable>();
		sList.add(new Statement(1000L,1,"handleCurrentChange(val) {"));
		sList.add(new Statement(2000L,1,"this."+listQuery.getVarName()+".rows = val"));
		sList.add(new Statement(3000L,1,"this.getList()"));
		sList.add(new Statement(4000L,1,"},"));
		return WriteableUtil.merge(sList);
	}
	
	public static StatementList generateHandleCheckedMethodStatements() {
		List<Writeable> sList = new ArrayList<Writeable>();
		sList.add(new Statement(1000L,1,"handleChecked(data) {"));
		sList.add(new Statement(2000L,1,"this.selectList = data;"));
		sList.add(new Statement(3000L,1,"},"));
		return WriteableUtil.merge(sList);
	}
	
	public static StatementList generateHandleCheckedAllMethodStatements(FrontDomain domain) {
		List<Writeable> sList = new ArrayList<Writeable>();
		sList.add(new Statement(1000L,1,"handleCheckedAll(data) {"));
		sList.add(new Statement(2000L,1,"this.selectList = data;"));
		sList.add(new Statement(3000L,1,"},"));
		return WriteableUtil.merge(sList);
	}
	
	public static StatementList generateSelectedHighlightMethodStatements() {
		List<Writeable> sList = new ArrayList<Writeable>();
		sList.add(new Statement(1000L,1,"selectedHighlight({"));
		sList.add(new Statement(2000L,1,"row,"));
		sList.add(new Statement(3000L,1,"rowIndex"));
		sList.add(new Statement(4000L,1,"}) {"));
		sList.add(new Statement(5000L,1,"if (this.selectRows.includes(rowIndex)) {"));
		sList.add(new Statement(6000L,2,"return {"));
		sList.add(new Statement(7000L,2,"\"background-color\": \"#a1c3c0\""));
		sList.add(new Statement(8000L,2,"};"));
		sList.add(new Statement(9000L,1,"} else {"));
		sList.add(new Statement(10000L,2,"return {"));
		sList.add(new Statement(11000L,2,"\"background-color\": \"#e8ebd0\""));
		sList.add(new Statement(12000L,2,"};"));
		sList.add(new Statement(13000L,1,"}"));
		sList.add(new Statement(14000L,1,"},"));
		return WriteableUtil.merge(sList);
	}
	
	public static StatementList generateHandleCloseMethodStatements() {
		List<Writeable> sList = new ArrayList<Writeable>();
		sList.add(new Statement(1000L,1,"handleClose(done) {"));
		sList.add(new Statement(2000L,1,"this.$confirm('确认关闭？')"));
		sList.add(new Statement(3000L,2,".then(_ => {"));
		sList.add(new Statement(4000L,2,"done();"));
		sList.add(new Statement(5000L,2,"})"));
		sList.add(new Statement(6000L,2,".catch(_ => {});"));
		sList.add(new Statement(7000L,1,"},"));
		return WriteableUtil.merge(sList);
	}
	
	public static StatementList generateShowAddDialogMethodStatements() {
		List<Writeable> sList = new ArrayList<Writeable>();
		sList.add(new Statement(1000L,1,"showAddDialog(){"));
		sList.add(new Statement(3000L,1,"this.form = {};"));
		sList.add(new Statement(4000L,1,"this.addDialogVisible = true"));
		sList.add(new Statement(5000L,1,"},"));
		return WriteableUtil.merge(sList);
	}
	
	public static StatementList generateShowEditDialogMethodStatements() {
		List<Writeable> sList = new ArrayList<Writeable>();
		sList.add(new Statement(1000L,1,"showEditDialog(){"));
		sList.add(new Statement(3000L,1,"this.form = this.selectList[0];"));
		sList.add(new Statement(4000L,1,"this.editDialogVisible = true"));
		sList.add(new Statement(5000L,1,"},"));
		return WriteableUtil.merge(sList);
	}
	
	public static StatementList generateTranslateDomainMethodStatements(FrontDomain domain) {
		List<Writeable> sList = new ArrayList<Writeable>();
		sList.add(new Statement(1000L,1,"translate"+domain.getCapFirstDomainName()+"("+domain.getLowerFirstDomainName()+"Id){"));
		sList.add(new Statement(2000L,2,"for (var i=0;i<this.active"+domain.getCapFirstPlural()+".length;i++){"));
		sList.add(new Statement(3000L,3,"if (this.active"+domain.getCapFirstPlural()+"[i].id == "+domain.getLowerFirstDomainName()+"Id) {"));
		sList.add(new Statement(4000L,4,"this."+domain.getLowerFirstDomainName()+" = this.active"+domain.getCapFirstPlural()+"[i];"));
		sList.add(new Statement(5000L,4,"return;"));
		sList.add(new Statement(6000L,3,"}"));
		sList.add(new Statement(7000L,2,"}"));
		sList.add(new Statement(8000L,2,"this."+domain.getLowerFirstDomainName()+" = {};"));
		sList.add(new Statement(9000L,1,"},"));
		return WriteableUtil.merge(sList);
	}
}


